home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 2 / Apprentice-Release2.iso / Source Code / C / Libraries / MacWT 0.04 / wt / x11graphics.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-10-31  |  5.6 KB  |  220 lines  |  [TEXT/MMCC]

  1. /*
  2. **  wt -- a 3d game engine
  3. **
  4. **  Copyright (C) 1994 by Chris Laurel
  5. **  email:  claurel@mr.net
  6. **  snail mail:  Chris Laurel, 5700 W Lake St #208,  St. Louis Park, MN  55416
  7. **
  8. **  This program is free software; you can redistribute it and/or modify
  9. **  it under the terms of the GNU General Public License as published by
  10. **  the Free Software Foundation; either version 2 of the License, or
  11. **  (at your option) any later version.
  12. **
  13. **  This program is distributed in the hope that it will be useful,
  14. **  but WITHOUT ANY WARRANTY; without even the implied warranty of
  15. **  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  16. **  GNU General Public License for more details.
  17. **
  18. **  You should have received a copy of the GNU General Public License
  19. **  along with this program; if not, write to the Free Software
  20. **  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  21. */
  22.  
  23.  
  24. #include <stdio.h>
  25. #include <X11/Xlib.h>
  26. #include <X11/Xutil.h>
  27. #include <sys/ipc.h>
  28. #ifndef NO_XSHM
  29. #include <sys/shm.h>
  30. #include <X11/extensions/XShm.h>
  31. #endif
  32.  
  33. #include "wt.h"
  34. #include "error.h"
  35. #include "wtmem.h"
  36. #include "framebuf.h"
  37. #include "graphics.h"
  38.  
  39.  
  40. static void create_window(void);
  41. static void load_palette(void);
  42. static void map_shared_mem(void);
  43.  
  44. Display *display;
  45. int screen;
  46. Window wtwin;
  47. static GC gc;
  48. #ifndef NO_XSHM
  49. static XShmSegmentInfo xshminfo;
  50. #endif
  51. static XImage *image;
  52. static unsigned char *image_mem;
  53. static int graphics_initialized = 0;
  54.  
  55.  
  56. void init_graphics(void)
  57. {
  58.      if (graphics_initialized == 1)
  59.       return;
  60.  
  61.      image_mem = wtmalloc(SCREEN_HEIGHT * SCREEN_WIDTH);
  62.      create_window();
  63.      load_palette();
  64.      map_shared_mem();
  65.  
  66.      graphics_initialized = 1;
  67. }
  68.  
  69.  
  70. static void create_window(void)
  71. {
  72.      XGCValues gc_values;
  73.  
  74.      display = XOpenDisplay(NULL);
  75.      if (display == NULL)
  76.       fatal_error("Unable to open display.\n");
  77.  
  78.      screen = DefaultScreen(display);
  79.      wtwin = XCreateSimpleWindow(display, DefaultRootWindow(display),
  80.                  0, 0, SCREEN_WIDTH, SCREEN_HEIGHT,
  81.                  2, BlackPixel(display, screen),
  82.                  BlackPixel(display, screen));
  83.      XStoreName(display, wtwin, "xwt");
  84.      XMapWindow(display, wtwin);
  85.      XSelectInput(display, wtwin,
  86.           ButtonPressMask | ButtonReleaseMask |
  87.           ButtonMotionMask | KeyPressMask | ExposureMask);
  88.      gc_values.graphics_exposures = False;
  89.      gc = XCreateGC(display, wtwin, GCGraphicsExposures, &gc_values);
  90. }
  91.  
  92.  
  93. static void load_palette(void)
  94. {
  95.      FILE *fp;
  96.      int i, r, g, b;
  97.      XColor palette[PALETTE_ENTRIES];
  98.      Colormap wtcolormap;
  99.      XVisualInfo *visual_info_list; 
  100.      XVisualInfo desired_visual_template;
  101.      int no_visual_matched;
  102.    
  103.  
  104.      fp = fopen(DEFAULT_PALETTE_FILE, "rb");
  105.      if (fp == NULL)
  106.       fatal_error("unable to open palette file");
  107.  
  108.      for (i = 0; i < PALETTE_ENTRIES; i++) {
  109.       r = getc(fp);
  110.       g = getc(fp);
  111.       b = getc(fp);
  112.       if (b == EOF)
  113.            fatal_error("error reading palette file");
  114.  
  115.       palette[i].pixel = i;
  116.       palette[i].red = r << 10;
  117.       palette[i].green = g << 10;
  118.       palette[i].blue = b << 10;
  119.       palette[i].flags = DoRed | DoGreen | DoBlue;
  120.      }
  121.      
  122.      fclose(fp);
  123.  
  124.      desired_visual_template.screen = screen;
  125.      desired_visual_template.class = PseudoColor;
  126.      visual_info_list = XGetVisualInfo(display, 
  127.                        VisualScreenMask | VisualClassMask,
  128.                        &desired_visual_template,
  129.                        &no_visual_matched);
  130.      if (no_visual_matched == 0)
  131.       fatal_error("Unable to get a PseudoColor Visual.\n");
  132.  
  133.      wtcolormap = XCreateColormap(display, DefaultRootWindow(display),
  134.                   visual_info_list[0].visual, AllocAll);
  135.      XStoreColors(display, wtcolormap, palette, PALETTE_ENTRIES);
  136.      XSetWindowColormap(display, wtwin, wtcolormap);
  137. }
  138.  
  139.  
  140. #ifdef NO_XSHM
  141. void map_shared_mem(void)
  142. {
  143.      int depth;
  144.      XWindowAttributes win_attributes;
  145.  
  146.      XGetWindowAttributes(display, DefaultRootWindow(display),
  147.                           &win_attributes);
  148.      depth = win_attributes.depth;
  149.      image = XCreateImage(display, DefaultVisual(display, screen), depth,
  150.                              ZPixmap, 0,image_mem,SCREEN_WIDTH,
  151.                              SCREEN_HEIGHT,8,0);
  152. }
  153.  
  154.  
  155. void update_screen(Framebuffer *fb)
  156. {
  157.      XPutImage(display, wtwin, gc, image, 0, 0, 0, 0,
  158.                   fb->fb_width, fb->fb_height);
  159.      XSync(display, 0);
  160. }
  161.  
  162.  
  163. void end_graphics(void)
  164. {
  165.    graphics_initialized = 0;
  166. }
  167. #else
  168. static void map_shared_mem(void)
  169. {
  170.      int depth;
  171.      XWindowAttributes win_attributes;
  172.  
  173.      XGetWindowAttributes(display, DefaultRootWindow(display),
  174.               &win_attributes);
  175.      depth = win_attributes.depth;
  176.      image = XShmCreateImage(display, DefaultVisual(display, screen), depth,
  177.                 ZPixmap, image_mem, &xshminfo,
  178.                 SCREEN_WIDTH, SCREEN_HEIGHT);
  179.      xshminfo.shmid = shmget(IPC_PRIVATE,
  180.                 image->bytes_per_line * image->height,
  181.                 IPC_CREAT | 0777);
  182.      if (xshminfo.shmid < 0)
  183.       fatal_error("shmget failed");
  184.      
  185.      image->data = (unsigned char *) shmat(xshminfo.shmid, 0, 0);
  186.      if (image->data == ((char *) -1))
  187.       fatal_error("shmat failed");
  188.      
  189.      image_mem = image->data;
  190.      xshminfo.shmaddr = image->data;
  191.      xshminfo.readOnly = False;
  192.      if (!XShmAttach(display, &xshminfo))
  193.       fatal_error("Unable to map shared memory.\n");
  194. }
  195.  
  196.  
  197. void update_screen(Framebuffer *fb)
  198. {
  199.      XShmPutImage(display, wtwin, gc, image, 0, 0, 0, 0,
  200.           fb->fb_width, fb->fb_height, 0);
  201.      XSync(display, 0);
  202. }
  203.  
  204.  
  205. void end_graphics(void)
  206. {
  207.    XShmDetach(display, &xshminfo);
  208.    XDestroyImage(image);
  209.    shmdt(xshminfo.shmaddr);
  210.    shmctl(xshminfo.shmid, IPC_RMID, 0);
  211.    graphics_initialized = 0;
  212. }
  213. #endif
  214.  
  215.  
  216. Pixel *get_framebuffer_memory(int width, int height)
  217. {
  218.      return (Pixel *) image_mem;
  219. }
  220.